<!--
 * @Description: ------------ fileDescription -----------
 * @Author: snows_l snows_l@163.com
 * @Date: 2024-03-26 14:55:27
 * @LastEditors: snows_l snows_l@163.com
 * @LastEditTime: 2025-01-08 10:28:47
 * @FilePath: \WebsiteUI\src\views\favors\index.vue
-->
<template>
  <div class="container-warp">
    <div class="select-warp">
      <el-form
        :model="state.form"
        ref="form"
        :rules="state.rules"
        :inline="true"
        :label-width="state.isMobile ? '0px' : ''"
        style="display: flex; align-items: center"
        :style="{ justifyContent: state.isMobile ? 'space-around' : 'flex-start' }">
        <el-form-item :style="{ width: state.isMobile ? '50%' : '' }" :label="state.isMobile ? '' : '姓名:'">
          <el-input style="min-width: 160px" v-model="state.form.name" clearable placeholder="请输入姓名" @change="handleSelect"></el-input>
        </el-form-item>

        <el-form-item :style="{ width: state.isMobile ? '46%' : '', marginLeft: !state.isMobile ? '30px' : '' }" :label="state.isMobile ? '' : '来往时间点:'">
          <el-select style="min-width: 160px" v-model="state.form.dictType" placeholder="请选择来往时间点" clearable @change="handleSelect">
            <el-option v-for="item in state.timerList" :key="item.value" :label="item.label" :value="item.value"></el-option>
          </el-select>
        </el-form-item>

        <el-form-item v-if="!state.isMobile" :style="{ margin: state.isMobile ? '0 10px 0 0' : '10px 0 10px 20px' }">
          <el-button @click="handleReset">重置</el-button>
          <el-button type="primary" @click="handleSelect">查询</el-button>
        </el-form-item>
      </el-form>
    </div>
    <div class="table-warp">
      <div class="operation-warp" style="margin-bottom: 15px">
        <div class="left" style="display: flex">
          <el-button type="primary" @click="handleAdd">添 加</el-button>
          <el-upload
            v-loading="state.uploadLoading"
            v-show="state.user.role_key != 'admin'"
            ref="uploadRef"
            style="margin-left: 10px"
            :limit="1"
            :auto-upload="false"
            :show-file-list="false"
            accept=".xlsx"
            :on-change="handleFileChange">
            <template #trigger>
              <el-button type="primary">批量导入</el-button>
            </template>
          </el-upload>
          <div class="admin-import" v-show="state.user.role_key == 'admin'" style="margin-left: 20px; display: flex; align-items: center">
            <el-button type="primary" @click="handleImport">批量导入</el-button>
          </div>
        </div>
        <div class="right">
          <el-button plain type="primary" v-loading="state.exportLoading" @click="handleExport">导 出</el-button>
          <el-button plain type="primary" v-loading="state.exportLoading" @click="downloadTemplateFn">下载模版</el-button>
        </div>
      </div>
      <div class="table-content-container">
        <el-table
          :data="state.tableSource"
          stripe
          :row-class-name="tableRowClassName"
          style="width: 100%; height: 100%"
          v-loading="state.loading"
          :size="state.isMobile ? 'small' : ''">
          <el-table-column
            v-for="col in columns"
            :prop="col.prop"
            :key="col.id"
            :label="col.label"
            :minWidth="col.minWidth"
            :align="col.align || 'center'"
            :fixed="col.fixed || null">
            <template #default="{ row }">
              <template v-if="col.prop == 'favors_timer'">
                <el-tag
                  v-if="state.timerObj[row[col.prop]]"
                  :type="(timerType[row[col.prop]] && timerType[row[col.prop]].type) || 'primary'"
                  :effect="(timerType[row[col.prop]] && timerType[row[col.prop]].effect) || 'light'">
                  {{ state.timerObj[row[col.prop]] }}
                </el-tag>
                <span v-else class="content-empty">无</span>
              </template>

              <template v-else-if="col.prop == 'remark'">
                <el-tooltip v-if="row[col.prop]" :content="row[col.prop]" placement="top" effect="dark">
                  <div
                    class="remark-warp"
                    style="line-height: 15px; overflow: hidden; text-overflow: ellipsis; display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical">
                    {{ row[col.prop] }}
                  </div>
                </el-tooltip>
                <span v-else class="content-empty">无</span>
              </template>

              <template v-else-if="col.prop == 'operation'">
                <el-button :size="state.isMobile ? 'small' : ''" type="primary" link @click="handleEdit(row)">编辑</el-button>
                <el-button :size="state.isMobile ? 'small' : ''" type="primary" link @click="handleDel(row)">删除</el-button>
              </template>
              <template v-else>
                <span v-if="row[col.prop]">{{ row[col.prop] }}</span>
                <span v-else class="content-empty">无</span>
              </template>
            </template>
          </el-table-column>

          <template #empty>
            <empty></empty>
          </template>
        </el-table>
      </div>
      <div class="footer-pagination">
        <el-pagination
          :size="state.isMobile ? 'small' : 'default'"
          :pager-count="state.isMobile ? 5 : 9"
          :background="state.isMobile ? false : true"
          v-model:current-page="state.page.page"
          v-model:page-size="state.page.size"
          :page-sizes="[20, 50, 100, 200]"
          :layout="state.isMobile ? 'total, prev, pager, next' : 'total, sizes, prev, pager, next, jumper'"
          :total="state.page.total"
          @size-change="handleSizeChange"
          @current-change="handleCurrentChange" />
      </div>
    </div>
    <EditDialog ref="editRef" @rereshCallback="getListFn" :is-mobile="state.isMobile" />

    <XDialog draggable title="导入收入明细" v-model="state.open" :size="state.isMobile ? '90vw' : '40%'" :before-close="handleClose">
      <div class="export-warp" style="padding: 0 20px 20px 20px">
        <el-form :model="state.importForm" ref="importFormRef" :rules="state.importRules" label-width="80px" :inline="false">
          <el-form-item label="所属角色" prop="role_key">
            <el-select style="width: 80%" v-model="state.importForm.role_key" placeholder="请选择所属角色" clearable>
              <el-option v-for="item in state.roleList" :key="item.role_key" :label="item.role_name" :value="item.role_key"></el-option>
            </el-select>
          </el-form-item>
          <el-form-item label="上传文件" style="margin-top: 30px">
            <el-button v-loading="state.importLoading" type="primary" size="default" @click="handleUpload">文件选择</el-button>
          </el-form-item>
        </el-form>
      </div>
      <template #footer>
        <span>
          <el-button @click="handleClose">取消</el-button>
        </span>
      </template>
    </XDialog>
  </div>
</template>

<script setup>
import { delFavors, exportFavors, getFavorsList, downloadTemplate, importFavors } from '@/api/favors';
import { getDictDetail } from '@/api/system/dict';
import { getRoleList } from '@/api/system/role';
import { local } from '@/utils/cache';
import { isMobile } from '@/utils/common';
import { ElMessage, ElMessageBox } from 'element-plus';
import moment from 'moment';
import { onUnmounted, reactive, ref } from 'vue';
import EditDialog from './editDialog.vue';
import { useAppStore } from '@/store/common';

const uploadRef = ref(null);
const importFormRef = ref(null);

const timerType = {
  1: { type: 'primary', effect: 'light' },
  2: { type: 'warning', effect: 'light' },
  3: { type: 'warning', effect: 'light' },
  4: { type: 'info', effect: 'light' }
};
let state = reactive({
  user: useAppStore().user,
  isMobile: isMobile(1000),
  loading: false,
  exportLoading: false,
  form: {
    name: '',
    dictType: ''
  },
  tableSource: [],
  rules: {},
  timerList: [],
  page: {
    page: 1,
    size: 50,
    total: 0
  },
  timerObj: {},
  roleList: [],

  // 导入
  open: false,
  importForm: {
    role_key: '',
    role_str: ''
  },
  importRules: {
    role_key: [{ required: true, message: '请选择所属角色', trigger: 'change' }]
  },
  importLoading: false
});

let tableHeight = ref(state.isMobile ? 'calc(100% - 82px)' : 'calc(100% - 82px)');

const columns = [
  { id: 2, label: '姓名', minWidth: '80px', prop: 'favors_name', align: 'center' },
  { id: 3, label: '金额', minWidth: '80px', prop: 'favors_money', align: 'center' },
  { id: 4, label: '回礼', minWidth: '80px', prop: 'favors_backMoney', align: 'center' },
  { id: 5, label: '时间点', minWidth: '90px', prop: 'favors_timer' },
  { id: 8, label: '归属角色', minWidth: '120px', prop: 'role_key' },
  { id: 8, label: '归属角色名', minWidth: '120px', prop: 'role_str' },
  { id: 6, label: '创建时间', minWidth: '120px', prop: 'createTime' },
  { id: 8, label: '更新时间', minWidth: '120px', prop: 'updateTime' },
  { id: 7, label: '备注', minWidth: '120px', prop: 'remark' },
  { id: 10, label: '操作', minWidth: state.isMobile ? '120px' : '120px', prop: 'operation', fixed: state.isMobile ? null : 'right' }
];

let userInfo = local.get('userInfo') || {};
if (userInfo?.user?.role_key == 'admin' || userInfo?.user?.role_key == '') {
  // columns.push({ id: 10, label: '操作', minWidth: state.isMobile ? '120px' : '120px', prop: 'operation', fixed: state.isMobile ? null : 'right' });
}

const editRef = ref(null);
// 编辑
const handleEdit = row => {
  editRef.value.init('edit', row, state.timerList);
};

// 新增
const handleAdd = () => {
  editRef.value.init('add', false, state.timerList);
};

// 删除
const handleDel = row => {
  ElMessageBox.confirm('此操作将永久删除该记录, 是否确认删除该记录吗？', '提示', { type: 'warning' }).then(() => {
    delFavors(row.favors_id).then(res => {
      if (res.code == 200) {
        ElMessage.success('删除成功');
        getListFn();
      } else {
        alert(res.msg);
      }
    });
  });
};

// 获取角色列表
const getRoleListFn = () => {
  getRoleList().then(res => {
    if (res.code == 200) {
      state.roleList = res.data;
    }
  });
};
getRoleListFn();

// 设置类名
const tableRowClassName = ({ row }) => {
  if (row.favors_backMoney) return 'back-money';
  else return '';
};

// 获取来往时间点下拉框
const getDictFn = () => {
  getDictDetail({ dictType: 'favors_time' }).then(res => {
    state.timerList = res.data;
    state.timerList.forEach((item, index) => {
      state.timerObj[item.value] = item.label;
    });
  });
};
getDictFn();

// admin 点击批量导入
const handleImport = () => {
  state.open = true;
};

// 弹窗点击选择文件
const handleUpload = () => {
  importFormRef.value.validate(valid => {
    if (valid) {
      state.importForm.role_str = state.roleList.find(item => item.role_key == state.importForm.role_key)?.role_name;
      uploadRef.value.$el.querySelector('input').click();
    }
  });
};

// 弹窗关闭
const handleClose = () => {
  state.open = false;
};

// 获取列表
const getListFn = () => {
  state.loading = true;
  let params = {
    dictType: state.form.dictType,
    name: state.form.name,
    page: state.page.page,
    size: state.page.size
  };
  getFavorsList(params)
    .then(res => {
      moment.suppressDeprecationWarnings = true;
      state.tableSource = res.data;
      state.tableSource.forEach(item => {
        item.createTime = item.create_time && moment(item.create_time).format('YYYY-MM-DD HH:mm:ss');
        item.updateTime = item.update_time && moment(item.update_time).format('YYYY-MM-DD HH:mm:ss');
      });
      state.page.total = res.total;
      state.loading = false;
    })
    .catch(() => {
      state.loading = false;
    });
};
getListFn();

const handleSizeChange = size => {
  state.page.page = 1;
  state.page.size = size;
  getListFn();
};

const handleCurrentChange = page => {
  state.page.page = page;
  getListFn();
};

// 查询
const handleSelect = () => {
  state.page.page = 1;
  getListFn();
};

const handleReset = () => {
  state.form.name = '';
  state.form.dictType = '';
  getListFn();
};

// 导入
const handleFileChange = file => {
  if (file) {
    state.importLoading = true;
    importFavors({ file: file.raw, role_key: state.importForm.role_key, role_str: state.importForm.role_str })
      .then(res => {
        if (res.code == 200) {
          ElMessage.success('导入成功');
          getListFn();
          handleClose();
        } else {
          ElMessage.error(res.msg);
        }
      })
      .finally(() => {
        uploadRef.value.clearFiles();
        state.importLoading = false;
      });
  }
};

// 导出技能表
const handleExport = () => {
  state.exportLoading = true;
  exportFavors()
    .then(res => {
      const link = document.createElement('a');
      const blob = new Blob([res], { type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet' });
      link.style.display = 'none';
      link.href = URL.createObjectURL(blob);
      link.download = '人情记录_' + moment().format('YYYYMMDDHHmmss') + '.xlsx';
      document.body.appendChild(link);
      link.click();
      document.body.removeChild(link);
      ElMessage.success('人情记录导出成功！');
    })
    .finally(() => {
      state.exportLoading = false;
    });
};

// 下载模板
const downloadTemplateFn = () => {
  state.exportLoading = true;
  downloadTemplate()
    .then(res => {
      const link = document.createElement('a');
      const blob = new Blob([res], { type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet' });
      link.style.display = 'none';
      link.href = URL.createObjectURL(blob);
      link.download = '人情模版_' + moment().format('YYYYMMDDHHmmss') + '.xlsx';
      document.body.appendChild(link);
      link.click();
      document.body.removeChild(link);
      ElMessage.success('人情模版下载成功！');
    })
    .finally(() => {
      state.exportLoading = false;
    });
};

const resizeCallback = () => {
  state.isMobile = isMobile(1000);
  tableHeight.value = state.isMobile ? 'calc(100% - 82px)' : 'calc(100% - 82px)';
};
window.addEventListener('resize', resizeCallback);

onUnmounted(() => {
  window.removeEventListener('resize', resizeCallback);
});
</script>

<style lang="scss" scoped>
.container-warp {
  width: 100%;
  height: 100% !important;
  overflow: hidden;
  background-color: var(--containerBgc);
  .select-warp {
    padding: 10px 20px;
    background-color: var(--contentBgc);
    .el-form-item {
      margin: 10px 0;
    }
  }
  .table-warp {
    height: v-bind(tableHeight);
    margin-top: 10px;
    padding: 20px 20px;
    background-color: var(--contentBgc);
    overflow: hidden;
    .table-content-container {
      height: calc(100% - 99px);
      overflow-y: auto;
    }
  }
}
.footer-pagination {
  border-top: 1px solid #ccc;
  padding: 20px 0px 0 20px;
  display: flex;
  justify-content: flex-end;
}
.operation-warp {
  display: flex;
  justify-content: space-between;
  margin-bottom: 20px;
}
</style>

<style>
.el-table .back-money > td {
  --el-table-tr-bg-color: #61d8b0ae !important;
  background-color: #61d8b0ae !important;
}
</style>
